package com.sa07.net;

import java.nio.ByteBuffer;

import com.sa07.exception.SatpDataInvalidException;

/**
 * Sap包
 * 
 * @author Long.shangbo
 * 
 *         2014-2-19 下午10:08:44
 */
public class SatpPacket {

	/**
	 * 包头
	 */
	private SatpPacketHeader header = null;

	/**
	 * 内容字节数组
	 */
	private byte[] content = null;

	/**
	 * crc16校验算法
	 */
	private short crc16Code = 0;

	private byte[] packetDatas = null;

	public SatpPacket(SatpPacketHeader header, byte[] content) {
		this.header = header;
		this.content = content;
		// 计算CRC16码
		calcCrc16Code();
		byte[] crcBytes = getCrc16CodeBytes();
		// 合并数据
		this.packetDatas = new byte[SatpPacketHeader.SATP_PACKET_HEADER_LEN
				+ content.length + 2];
		System.arraycopy(header.getByteData(), 0, packetDatas, 0,
				SatpPacketHeader.SATP_PACKET_HEADER_LEN);
		System.arraycopy(crcBytes, 0, packetDatas, 0, 2);
	}

	public SatpPacketHeader getHeader() {
		return header;
	}

	public byte[] getPacketDatas() {
		return packetDatas;
	}
	
	public ByteBuffer getPacketBuffer(){
		ByteBuffer bf = ByteBuffer.wrap(packetDatas);
		bf.flip();
		return bf;
	}

	public void setPacketDatas(byte[] packetDatas) {
		if (packetDatas == null
				|| packetDatas.length <= SatpPacketHeader.SATP_PACKET_HEADER_LEN) {
			throw new SatpDataInvalidException("Satp data invalid...");
		}

		this.packetDatas = packetDatas;
		// 获取头部
		byte[] headerBytes = new byte[SatpPacketHeader.SATP_PACKET_HEADER_LEN];
		System.arraycopy(packetDatas, 0, headerBytes, 0,
				SatpPacketHeader.SATP_PACKET_HEADER_LEN);
		this.header = new SatpPacketHeader();
		this.header.setByteData(headerBytes);

		// 获取内容字节
		// 获取content内容的长度(减去命令序列和是否有后续命令的长度)
		int contentLen = this.header.getLen() - 1 - 1;
		byte[] contentBytes = new byte[contentLen];
		System.arraycopy(packetDatas,
				SatpPacketHeader.SATP_PACKET_HEADER_LEN + 1, contentBytes, 0,
				contentLen);
		this.content = contentBytes;

		// 获取crc16算法值
		byte[] crc16Bytes = new byte[2];
		System.arraycopy(packetDatas, SatpPacketHeader.SATP_PACKET_HEADER_LEN
				+ contentLen + 1, crc16Bytes, 0, 2);
	}

	public void setHeader(SatpPacketHeader header) {
		this.header = header;
	}

	public byte[] getContent() {
		return content;
	}

	public void setContent(byte[] content) {
		this.content = content;
	}

	public short getCrc16Code() {
		return crc16Code;
	}

	public void setCrc16Code(short crc16Code) {
		this.crc16Code = crc16Code;
	}

	/**
	 * 获得crc16校验码字节数组
	 * 
	 * @return
	 */
	private byte[] getCrc16CodeBytes() {
		byte[] crcBytes = new byte[2];
		crcBytes[0] = (byte) (crc16Code >> 8 & 0xff);
		crcBytes[1] = (byte) (crc16Code & 0xff);
		return crcBytes;
	}

	/**
	 * 计算CRC16码
	 */
	private void calcCrc16Code() {

	}
}
